#region - Class details -
/*  
 *  Developer   : Wicus Botha
 *  Description : 
 *  History     : WB - 2008-01-08 - Created
 */
#endregion

using System;
using System.IO;
using System.Text;

namespace IQ.DbBase
{
	/// <summary>
	/// Description of ConnectionProperties.
	/// </summary>
	
	public class ConnectionProperties
	{
		#region # Constructor # 
		public ConnectionProperties()
		{
			server = "";
			UserID = "";
			Password = "";
			Driver = "";
			Port = "";
			Name = "";
			IntegratedSecurity = false;
		}
		#endregion
		
		#region - Private variables -
		private string server;
        private bool canConnect = false;
        private string database = "";
		#endregion 
		
		#region - Private methods - 
		private string getSectionValue(string connectionStr, string sectionToGet)
		{	
			int iPos = connectionStr.ToLower().IndexOf(sectionToGet.ToLower());
			if (sectionToGet == "")
				iPos = -1;
			if (iPos >= 0) // Section found
			{
				iPos += sectionToGet.Length;
				int iPosEnd = connectionStr.IndexOf(';',iPos);
				if (iPosEnd == -1)
					return "";
				else
				{
					if (iPosEnd == 0)					
						iPosEnd = connectionStr.Length;				
					return connectionStr.Substring(iPos,iPosEnd-iPos);
				}
			}
			else // Section Not found
			{
				return "";
			}			
		}	
		private string getSectionValueAll(string connectionStr, string sectionSQL, string sectionODBC)
		{
			string valueToGet = getSectionValue(connectionStr, sectionSQL); // Try Sql
			if (valueToGet == "")
				valueToGet = getSectionValue(connectionStr,sectionODBC) ; // Try ODBC
			return valueToGet;
		}
		#endregion
		
		#region - Public properties / variables - 
		public ConnectionTypes ConnectionType;
		public string Server
		{
			get { return this.server; }
			set { this.canConnect = false;
				  this.server = value; }
		}
        public string Database
        {
            get { return database; }
            set { 
                    database = value;
                    canConnect = false;
                }
        }
        public string UserID;
		public string Password;
		public string Driver;
		public string Port;
		public string Name;
        public string ApplicationName;
        public string ExtendedProperties;
		public bool IntegratedSecurity;
		public bool CanConnect
		{
			get{ return this.canConnect; }
		}
		#endregion
					
		#region - Public methods - 
		public static System.Data.Common.DbConnection GetConnection(ConnectionTypes connectionType,
		                                                            string connectionString)
		{
			switch (connectionType) 
			{
				case ConnectionTypes.SqlServer : return new System.Data.SqlClient.SqlConnection(connectionString);
				case ConnectionTypes.Odbc      : return new System.Data.Odbc.OdbcConnection(connectionString);
				case ConnectionTypes.OleDB     : return new System.Data.OleDb.OleDbConnection(connectionString);
				default: return null;							
			}
		}
		public System.Data.Common.DbConnection GetConnection()
		{
			return ConnectionProperties.GetConnection(this.ConnectionType, this.GetConnectionString());
		}	
		public string GetConnectionString()
		{
			if (Server == "")
				return "";
			else
			{
                string delimiter = ";";
                StringBuilder tmpCon = new StringBuilder();
				switch (this.ConnectionType)
				{
					case ConnectionTypes.SqlServer :
					case ConnectionTypes.OleDB :
						{
                            tmpCon.Append("Data Source=" + Server + delimiter);
							if (IntegratedSecurity)
								tmpCon.Append("Integrated Security=SSPI;Persist Security Info=False;");
							else
								tmpCon.Append("User ID="+UserID + ";Password="+ Password + ";Persist Security Info=True;");
							//
                            tmpCon.Append("Initial Catalog=" + Database + delimiter);// +";MultipleActiveResultSets=True";			 			  			 	
							if (this.ConnectionType == ConnectionTypes.OleDB)
                                tmpCon.Append("Provider=" + Driver + delimiter + tmpCon);
                            //
                            tmpCon.Append("Workstation ID=" + Environment.MachineName + delimiter);
                            break;
						}
					case ConnectionTypes.Odbc :
						{
                            tmpCon.Append("DRIVER=" + Driver + delimiter);
                            tmpCon.Append("Server="+Server + delimiter);
                            tmpCon.Append("Database="+Database + delimiter);
                            tmpCon.Append("Uid=" + UserID + delimiter);
                            tmpCon.Append("Pwd=" + Password + delimiter);
							if (Port != "")
                                tmpCon.Append("Port=" + Port + delimiter);
							break;
						}
                    default: tmpCon.Append(""); break;
				}
                if (!String.IsNullOrEmpty(ApplicationName))
                    tmpCon.Append("Application Name=" + ApplicationName + delimiter);
                if (!String.IsNullOrEmpty(ExtendedProperties))
                    tmpCon.Append("Extended Properties=" + ExtendedProperties + delimiter);
                //
                return tmpCon.ToString();
				// Add Connection Type to Connection string ??
				// return tmpCon += "ConnectionType=" +this.ConnectionType.ToString();
			}
		}
		public void SetConnectionString(string connectionStr)
		{			
			this.canConnect = false;
			// Get Server
			Server = getSectionValueAll(connectionStr,"Data Source=","Server=");
			// Get Database
			Database = getSectionValueAll(connectionStr,"Initial Catalog=","Database=");
			// Get UserID
			UserID = getSectionValueAll(connectionStr,"User ID=","Uid=");
			// Get Password
			Password = getSectionValueAll(connectionStr,"Password=","Pwd=");
			// Get Driver
			Driver = getSectionValueAll(connectionStr,"","Driver=");
			// Get Port
			Port = getSectionValueAll(connectionStr,"","Port=");
			// Get Inegrated Security
			IntegratedSecurity = (getSectionValueAll(connectionStr,"","Integrated Security=") != "");
		}
		public void SaveConnectionString(string fileName)
		{
			string result = "";
			string cs = this.GetConnectionString() +"ConnectionType=" + (int)ConnectionType;
			foreach (char c in cs)
			{				
				char ec = (char)((int)c + 100);
       			result += ec;
			}
			// Check if folder exists
			if (System.IO.Path.GetDirectoryName(fileName) != "" &&
				!System.IO.Directory.Exists(System.IO.Path.GetDirectoryName(fileName)))
				System.IO.Directory.CreateDirectory(fileName);
			StreamWriter sw = new StreamWriter(fileName, false); // Important: no encdoing!
			try
            {    
				sw.WriteLine(result);
			}
			finally
            {
            	sw.Close();              		
           	}
		}
		public void LoadConnectionString(string fileName)
		{
			this.canConnect = false;
			if (System.IO.File.Exists(fileName))
			{
				StreamReader sr = new StreamReader(fileName);
				try
            	{    
					string es = sr.ReadLine();
					string cs = "";
					foreach (char c in es)
					{				
						char ec = (char)((int)c - 100);
       					cs += ec;
					}
					//
					string ct = getSectionValue(cs,"ConnectionType");
					if (ct == ((int)ConnectionTypes.Odbc).ToString())
						ConnectionType = ConnectionTypes.Odbc;
					else
						ConnectionType = ConnectionTypes.SqlServer;
					//
					this.SetConnectionString(cs);
						
				}
				finally
            	{
            		sr.Close();              		
           		}
			}
		}
		public string TestConnection(System.Data.Common.DbConnection Connection)
		{
			this.canConnect = false;
			if (Connection != null)
			{
				try 
				{
					Connection.Open();
					this.canConnect = true;
                    Connection.Close();
					return "";
				} 
				catch (Exception e)
				{					
					this.canConnect = false;
					return e.Message;
				}
			}
			else
				return "Connection is emtpy";
		}
		public string TestConnectionString()
		{			
			System.Data.Common.DbConnection con = GetConnection();
			return TestConnection(con);		
		}	
		#endregion
	}
}
